import { _decorator, Component, Node, Vec2, input, Input, EventMouse, KeyCode, game, view } from 'cc';
import { inputConfig } from './input_config';
const { ccclass, property } = _decorator;

@ccclass('MouseInput')
export class MouseInput {
    // 映射变量
    protected _scroll: Vec2 | null = null;
    protected _inputKeys: Map<string, boolean>;
    protected _primaryMovment: Vec2 | null = null;

    // 临时变量
    protected _keyToInputMap: Map<number, string> = new Map();
    protected _mouseLocation: Vec2 = new Vec2;
    protected _minX = 0;
    protected _maxX = 0;
    protected _minY = 0;
    protected _maxY = 0;
    protected _fullScreen = false;

    constructor (primary: Vec2 | null, scroll: Vec2 | null, inputKeys: Map<string, boolean>) {
        this._primaryMovment = primary;
        this._scroll = scroll;
        this._inputKeys = inputKeys;

        input.on(Input.EventType.MOUSE_DOWN, this._onMouseDown, this);
        input.on(Input.EventType.MOUSE_MOVE, this._onMouseMove, this);
        input.on(Input.EventType.MOUSE_UP, this._onMouseUp, this);
        input.on(Input.EventType.MOUSE_WHEEL, this._onMouseWheel, this);

        this.convertInputConfig();

        if (game.canvas) {
            game.canvas.onfullscreenchange = () => {
                this._fullScreen = !this._fullScreen;
            };
        }

        let viewport = view.getViewportRect();
        this._minX = 0;
        this._maxX = viewport.width;
        this._minY = 0;
        this._maxY = viewport.height;
    }

    destory () {
        input.off(Input.EventType.MOUSE_DOWN, this._onMouseDown, this);
        input.off(Input.EventType.MOUSE_MOVE, this._onMouseMove, this);
        input.off(Input.EventType.MOUSE_UP, this._onMouseUp, this);
        input.off(Input.EventType.MOUSE_WHEEL, this._onMouseWheel, this);
        this._primaryMovment = null;
        this._scroll = null;
    }

    /**
     *  鼠标滚轮
     * @param event 
     */
    private _onMouseWheel (event: EventMouse) {
        this._scroll?.set(event.getScrollX(), event.getScrollY());
    }

    /**
     * 鼠标移动
     * @param event 
     */
    private _onMouseMove (event: EventMouse) {
        // this._mouseLocation.x += event.movementX;
        // this._mouseLocation.y -= event.movementY;

        // if (!this._fullScreen) {
        //     event.getLocation(this._mouseLocation);
        // }

        // if (this._mouseLocation.x < this._minX) {
        //     this._mouseLocation.x = this._minX;
        // }
        // if (this._mouseLocation.x > this._maxX) {
        //     this._mouseLocation.x = this._maxX;
        // }
        // if (this._mouseLocation.y < this._minY) {
        //     this._mouseLocation.y = this._minY;
        // }
        // if (this._mouseLocation.y > this._maxY) {
        //     this._mouseLocation.y = this._maxY;
        // }

        this._primaryMovment?.set(event.movementX, -event.movementY)
    }

    /**
     * 鼠标按键按下 
     * @param event 
     */
    private _onMouseDown (event: EventMouse) {
        let btnType = event.getButton();
        if (this._keyToInputMap.has(btnType)) {
            this._inputKeys.set(this._keyToInputMap.get(btnType)!, true)
        }
    }

    /**
     * 鼠标按键弹起
     * @param event 
     */
    private _onMouseUp (event: EventMouse) {
        let btnType = event.getButton();
        if (this._keyToInputMap.has(btnType)) {
            this._inputKeys.set(this._keyToInputMap.get(btnType)!, false)
        }
    }

    /**
     * 配置表转换
     */
    public convertInputConfig () {
        inputConfig.controlKeys.forEach((inputKey, control) => {
            let mouseCode = this._inputKey2MouseKey(inputKey);
            if (mouseCode) {
                this._keyToInputMap.set(mouseCode, control);
                this._inputKeys.set(control, false);
            }
        });
    }

    /**
     * 将配置表的输入按键转换为实际按键
     * @param key 
     * @returns 
     */
    private _inputKey2MouseKey (key: string) {
        key = key.toUpperCase();
        if (key.indexOf("MOUSE") != -1) {
            key = key.replace("MOUSE", "BUTTON");
            //@ts-ignore
            return EventMouse[`${key}`];
        }
        return 0;

    }
}

